package com.godenwater.recv.server.summit;

import com.godenwater.recv.model.CommonMessage;
import org.apache.mina.core.buffer.IoBuffer;
import org.apache.mina.core.session.AttributeKey;
import org.apache.mina.core.session.IoSession;
import org.apache.mina.filter.codec.CumulativeProtocolDecoder;
import org.apache.mina.filter.codec.ProtocolDecoderOutput;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.util.StringUtils;


/**
 * 报文解码类，作为上行报文的解码类，此类必须实现对所有消息体的封闭细节
 * 
 * @ClassName: YfServerDataDecoder
 * @Description: 处理断包和粘包的实现类
 * @author lipujun
 * @date Mar 2, 2013
 * 
 */
public class SummitServerDataDecoder extends CumulativeProtocolDecoder {
	private static final AttributeKey BUF_BYTE = new AttributeKey(
			SummitServerDataDecoder.class, "BUF_KEY");

	private Logger logger = LoggerFactory.getLogger(this.getClass());

	private String channel;

	public SummitServerDataDecoder(String channel) {
		this.channel = channel;
	}

	/**
	 * 这个办法的返回值是重点：
	 * <p>
	 * 1、当内容正好时，返回false，告诉父类可以进行下一批消息的处理
	 * <p>
	 * 2、内容不符时，需要下一批消息的内容，此时返回false
	 * ，如许父类会将内容放进IoSession中，等下次数据来后就主动拼装再交给本类的doDecode
	 * <p>
	 * 3、当内容多时，返回true，因为需要再将本批数据进行读取，父类会将残剩的数据再次推送本类的doDecode
	 * <p>
	 * 简而言之，当你认为读取到的数据已经够解码了，那么就返回true，否则就返回false。
	 */
	@Override
	protected boolean doDecode(IoSession session, IoBuffer buffer,
							   ProtocolDecoderOutput out) throws Exception {
		// 将此报文日志，记录到RTU单独的文件中，此类报文内容有可能会出现粘包的报文
		logger.info("R> " + this.channel + " " + StringUtils.trimAllWhitespace(buffer.getHexDump()));

		// logger.info(">> HEX : " +
		// ByteUtil.toHexString(buffer.buf().array()));

		CommonMessage message = new CommonMessage();

		int len = buffer.remaining();
		if (len > 0) {// 表示缓冲区中有数据
			// 组装消息
			byte[] body = new byte[len];
			buffer.get(body);

			message.setContent(body);
			out.write(message);
			return false;
		}
		return false;// 处理重发成功，让父类进行接管下个包
	}

	public void dispose(IoSession session) throws Exception {
		// TODO Auto-generated method stub

	}

	public void finishDecode(IoSession session, ProtocolDecoderOutput out)
			throws Exception {
		// TODO Auto-generated method stub

	}

}
